//
//  XPDateTimeSelector.swift
//  PPKit
//
//  Created by xiaopin on 2019/9/10.
//  Copyright © 2019 PPKit. All rights reserved.
//  https://gitee.com/xiaopindev/PPKit
//  https://github.com/xiaopindev
//  https://xiaopin.cnblogs.com

import UIKit

typealias XPDateTimeSelectorOkClosure = (_ value:String,_ valueStr:String)->Void

/// 日期选择类型
enum DateSelectStyle {
    /// 年：2020
    case year
    /// 年月：2020-12
    case yearMonth
    /// 年月日：2020-12-12
    case yearMonthDay
    /// 年月日时分：2020-12-12 12:12
    case yearMonthDayHourMin
    /// 时分：12:12
    case HourMin
}

class XPDateTimeSelector: XPBaseView,UIPickerViewDelegate,UIPickerViewDataSource {
    
    //MARK: 公开属性
    /// 选中回调
    public var okClosure:XPDateTimeSelectorOkClosure?
    
    //MARK: 私有属性
    /// 时间格式：yyyy-MM-dd HH:mm:00
    private var dtvalue:String {
        get{
            let selectedMonthFormat = String(format:"%.2d",selectedMonth)
            let selectedDayFormat = String(format:"%.2d",selectedDay)
            let selectedHourFormat = String(format:"%.2d",selectedHour)
            let selectedMinuteFormat = String(format:"%.2d",selectedMinute)
            switch selectStyle {
            case .year:
                return "\(selectedYear)"
            case .yearMonth:
                return "\(selectedYear)-\(selectedMonthFormat)"
            case .yearMonthDay:
                return "\(selectedYear)-\(selectedMonthFormat)-\(selectedDayFormat)"
            case .HourMin:
                return "\(selectedHourFormat):\(selectedMinuteFormat)"
            default:
                return "\(selectedYear)-\(selectedMonthFormat)-\(selectedDayFormat) \(selectedHourFormat):\(selectedMinuteFormat):00"
            }
        }
    }
    
    /// 时间格式：yyyy年MM月dd日 HH:mm
    private var dtvalueStr:String {
        get{
            let selectedMonthFormat = String(format:"%.2d",selectedMonth)
            let selectedDayFormat = String(format:"%.2d",selectedDay)
            let selectedHourFormat = String(format:"%.2d",selectedHour)
            let selectedMinuteFormat = String(format:"%.2d",selectedMinute)
            switch selectStyle {
            case .year:
                return "\(selectedYear)年"
            case .yearMonth:
                return "\(selectedYear)年\(selectedMonthFormat)月"
            case .yearMonthDay:
                return "\(selectedYear)年\(selectedMonthFormat)月\(selectedDayFormat)日"
            case .HourMin:
                return "\(selectedHourFormat):\(selectedMinuteFormat)"
            default:
                return "\(selectedYear)年\(selectedMonthFormat)月\(selectedDayFormat)日 \(selectedHourFormat):\(selectedMinuteFormat)"
            }
        }
    }
    
    /// 背景滤镜透明度
    private var bgTransparency:CGFloat = 0.5
    /// 选择样式
    private var selectStyle:DateSelectStyle = .yearMonthDayHourMin
    /// 年范围，当前年份后前加减这个范围
    private var yearRange = 30
    private var dayRange = 0
    private var startYear = 0
    private var selectedYear = 0
    private var selectedMonth = 0
    private var selectedDay = 0
    private var selectedHour = 0
    private var selectedMinute = 0
    private var selectedSecond = 0

    //MARK: 懒加载
    /// 透明背景视图
    private lazy var alphaView: UIView = {
        let view = UIView(frame: pp_frame(0,0,self.width,self.height))
        view.backgroundColor = UIColor.black.withAlphaComponent(bgTransparency)
        view.alpha = 0
        let tapGesture = UITapGestureRecognizer(target: self, action: #selector(closeAction))
        view.addGestureRecognizer(tapGesture)
        return view
    }()
    
    //内容视图
    private lazy var contentView: UIView = {
        let view = UIView(frame: pp_frame(0,self.height,self.width,300))
        view.backgroundColor = .white
        view.cornerRadius = 5
        return view
    }()
    
    //导航栏
    private lazy var navView: UIView = {
        let view = UIView(frame: pp_frame(0,0,self.width,44))
        view.backgroundColor = .white
        view.addSubview(labTitle)
        view.addSubview(btnClose)
        view.addSubview(btnOK)
        view.addSubview(navLine)
        return view
    }()
    
    //关闭按钮
    private lazy var btnClose: UIButton = {
        let button = UIButton(type: .custom)
        button.frame = pp_frame(0, 0,44, 44)
        button.setImage(UIImage(named:"close_7"), for: .normal)
        button.titleLabel?.font = UIFont.systemFont(ofSize: 15)
        button.addTarget(self, action: #selector(closeAction), for: .touchUpInside)
        return button
    }()
    
    //标题
    private lazy var labTitle: UILabel = {
        let label = UILabel(frame: pp_frame(0,0,width,44))
        label.text = "标题"
        label.textColor = #colorLiteral(red: 0.2, green: 0.2, blue: 0.2, alpha: 1)
        label.font = .systemFont(ofSize: 17)
        label.textAlignment = .center
        return label
    }()
    
    //OK
    private lazy var btnOK: UIButton = {
        let button = UIButton(type: .custom)
        button.frame = pp_frame(width - 54, 7, 44, 30)
        button.setTitle("确定", for: .normal)
        button.setTitleColor(#colorLiteral(red: 0.3921568627, green: 0.3921568627, blue: 0.3921568627, alpha: 1), for: .normal)
        button.titleLabel?.font = UIFont.systemFont(ofSize: 13)
        button.addTarget(self, action: #selector(okAction), for: .touchUpInside)
        button.cornerRadius = 5
        button.borderColor = Color_Gray3
        return button
    }()
    
    //导航栏分割线
    private lazy var navLine: UIView = {
        let view = UIView(frame: pp_frame(0,44,width,0.5))
        view.backgroundColor = Color_Gray2
        return view
    }()
    
    //文本框
    private lazy var pickerView: UIPickerView = {
        let picker = UIPickerView(frame: pp_frame(13,44,width-26,contentView.height - 44))
        picker.delegate = self
        picker.dataSource = self
        return picker
    }()
    
    //MARK: 重载父类方法
    
    /// 初始化时间选择器
    /// - Parameters:
    ///   - frame: <#frame description#>
    ///   - bgAlpha: 背景透明度：默认0.5半透明,0 全透明
    ///   - yearScope: 当前时间前后年范围，比如：当前2020， 时间是1910 - 2050，
    ///   - style: 样式类型
    convenience init(frame: CGRect,bgAlpha:CGFloat = 0.5,yearScope:Int = 30,style:DateSelectStyle = .yearMonth) {
        self.init(frame: frame)
        
        bgTransparency = bgAlpha
        yearRange = yearScope
        selectStyle = style
        
        initData()
        DispatchQueue.main.async {
            self.initSubViews()
        }
    }
    
    /// 初始化数据
    override func initData() {
        let  calendar0 = Calendar.init(identifier: .gregorian)//公历
        var comps = DateComponents()//一个封装了具体年月日、时秒分、周、季度等的类
        let unitFlags:Set<Calendar.Component> = [.year , .month , .day , .hour , .minute]
        comps = calendar0.dateComponents(unitFlags, from: Date())
        startYear = comps.year! - yearRange
    
        dayRange = isAllDay(year: startYear, month: 1)
        
        selectedYear = comps.year!
        selectedMonth = comps.month!
        selectedDay = comps.day!
        selectedHour = comps.hour!
        selectedMinute = comps.minute!
        
        switch selectStyle {
        case .year:
            pickerView.selectRow(selectedYear - startYear, inComponent: 0, animated: true)
        case .yearMonth:
            pickerView.selectRow(selectedYear - startYear, inComponent: 0, animated: true)
            pickerView.selectRow(selectedMonth-1, inComponent: 1, animated: true)
        case .yearMonthDay:
            pickerView.selectRow(selectedYear - startYear, inComponent: 0, animated: true)
            pickerView.selectRow(selectedMonth-1, inComponent: 1, animated: true)
            pickerView.selectRow(selectedDay-1, inComponent: 2, animated: true)
        case .HourMin:
            pickerView.selectRow(selectedYear - startYear, inComponent: 0, animated: true)
            pickerView.selectRow(selectedMonth-1, inComponent: 1, animated: true)
        default:
            pickerView.selectRow(selectedYear - startYear, inComponent: 0, animated: true)
            pickerView.selectRow(selectedMonth-1, inComponent: 1, animated: true)
            pickerView.selectRow(selectedDay-1, inComponent: 2, animated: true)
            pickerView.selectRow(selectedHour , inComponent: 3, animated: true)
            pickerView.selectRow(selectedMinute , inComponent: 4, animated: true)
        }
        pickerView.reloadAllComponents()
    }
    
    /// 初始化当前视图的子控件
    override func initSubViews() {
        addSubview(alphaView)
        addSubview(contentView)
        contentView.addSubview(navView)
        contentView.addSubview(pickerView)
    }
    
    //MARK: 自定义方法
    
    /// 弹出显示
    /// - Parameters:
    ///   - title: 标题
    ///   - value: 当前选中值
    func show(title:String? = "",value:String? = ""){
        labTitle.text = title
        UIView.animate(withDuration: 0.3, animations: {
            self.alphaView.alpha = 1
        }, completion: { (finished) in
            UIView.animate(withDuration: 0.3, animations: {
                self.contentView.top = self.height - self.contentView.height
            })
        })
    }
    
    ///计算每个月有多少天
    private func isAllDay(year:Int, month:Int) -> Int {
        var day:Int = 0
        switch(month) {
        case 1,3,5,7,8,10,12:
            day = 31
        case 4,6,9,11:
            day = 30
        case 2:
            if(((year%4==0)&&(year%100==0))||(year%400==0)){
                day = 29
            }else{
                day = 28
            }
        default:
            break;
        }
        return day;
    }
    
    //MARK: 事件通知
    
    @objc private func closeAction(){
        UIView.animate(withDuration: 0.3, animations: {
            self.contentView.top = pp_screen_height
        }, completion: { (finished) in
            UIView.animate(withDuration: 0.3, animations: {
                self.alphaView.alpha = 0
                self.removeFromSuperview()
            })
        })
    }
    
    @objc private func okAction(){
        if let closure = okClosure {
            closure(dtvalue,dtvalueStr)
        }
        closeAction()
    }
    
    //MARK: 委托代理
    func numberOfComponents(in pickerView: UIPickerView) -> Int {
        switch selectStyle {
        case .year:
            return 1
        case .yearMonth:
            return 2
        case .yearMonthDay:
            return 3
        case .HourMin:
            return 2
        default:
            return 5
        }
    }
    
    func pickerView(_ pickerView: UIPickerView, numberOfRowsInComponent component: Int) -> Int {
        switch component {
        case 0:
            return yearRange*2
        case 1:
            return 12
        case 2:
            return dayRange
        case 3:
            return 24
        case 4:
            return 60
        default:
            return 0
        }
    }
    
    func pickerView(_ pickerView: UIPickerView, viewForRow row: Int, forComponent component: Int, reusing view: UIView?) -> UIView {
        let label  = UILabel(frame: CGRect(x: pp_screen_width * CGFloat(component) / 6 , y: 0, width: pp_screen_width/6, height: 30))
        label.font = UIFont.systemFont(ofSize: 15)
        label.tag = component*100+row
        label.textAlignment = .center
        
        switch component {
        case 0:
            label.frame=CGRect(x:5, y:0,width:pp_screen_width/4.0, height:30)
            label.text="\(startYear + row)年"
        case 1:
            label.frame=CGRect(x:pp_screen_width/4.0, y:0,width:pp_screen_width/8.0, height:30)
            label.text="\(row + 1)月";
        case 2:
            label.frame=CGRect(x:pp_screen_width*3/8, y:0,width:pp_screen_width/8.0, height:30)
            label.text="\(row + 1)日";
        case 3:
            label.textAlignment = .right
            label.text="\(row )时";
        case 4:
            label.textAlignment = .right
            label.text="\(row )分";
        case 5:
            label.textAlignment = .right
            label.frame=CGRect(x:pp_screen_width/6, y:0,width:pp_screen_width/6.0 - 5, height:30)
            label.text="\(row )秒"
        default:
            label.text="\(row )秒"
        }
        return label
    }
    
    
    //当点击UIPickerView的某一列中某一行的时候，就会调用这个方法
    func pickerView(_ pickerView: UIPickerView, didSelectRow row: Int, inComponent component: Int) {
        switch component {
        case 0:
            selectedYear = startYear + row
            if selectStyle == .yearMonthDay || selectStyle == .yearMonthDayHourMin {
                dayRange = isAllDay(year: startYear, month: selectedMonth)
                pickerView.reloadComponent(2)
            }
        case 1:
            selectedMonth =  row + 1
            if selectStyle == .yearMonthDay || selectStyle == .yearMonthDayHourMin {
                dayRange = isAllDay(year: startYear, month: selectedMonth)
                pickerView.reloadComponent(2)
            }
        case 2:
            selectedDay = row + 1
        case 3:
            selectedHour = row
        case 4:
            selectedMinute = row
        case 5:
            selectedSecond = row
        default:
            selectedSecond = row
        }
    }
}
